/*
 * Copyright (C) ARM Limited, 2016. All rights reserved.
 */

/*
 * This file contains re-implementations of functions whose
 * C library implementations rely on semihosting.
 *
 * Define USE_SERIAL_PORT to retarget the I/O only to the serial port.
 * Otherwise, I/O is targeted to the debugger console using semihosting.
 *
 * Define STANDALONE to eliminate all use of semihosting-using functions too.
 */

#include <stdio.h>
#include <sys/stat.h>
#include <sys/errno.h>
#include "early_uart.h"
#include "smp.h"
#include "sdkconfig.h"

void initialise_monitor_handles()
{
    /* 关闭行缓冲 */
    setvbuf(stdout, NULL, _IONBF, 0);
    setvbuf(stdin, NULL, _IONBF, 0);
}

int _read(int file, char *ptr, int len)
{
    int i;
    (void)file;
    for (i = 0; i < len; ++i)
    {
        ptr[i] = GetByte();
    }
    return len;
}

int _write(int file, char *ptr, int len)
{
    int i;
    (void)file;

#ifdef CONFIG_USE_AMP
    SpinLock() ;
#endif
    for (i = 0; i < len; ++i)
    {
        if (ptr[i] == '\n')
        {
            OutByte('\r');
        }

        OutByte(ptr[i]);
    }
#ifdef CONFIG_USE_AMP
    SpinUnlock() ;
#endif
    return len;
}

int _lseek(int file, int ptr, int dir)
{
    (void)file;
    (void)ptr;
    (void)dir;
    errno = ESPIPE;
    return -1;
}

int _close(int file)
{
    (void)file;
    return -1;
}

int _fstat(int file, struct stat *st)
{
    (void)file;
    st->st_mode = S_IFCHR;
    return 0;
}

int _isatty(int fd)
{
    (void)fd;
    errno = ENOTTY;
    return 0;
}

void *_sbrk(int increment)
{
    extern char end; // From linker script
    static char *heap_end = &end;

    char *current_heap_end = heap_end;
    heap_end += increment;
    return current_heap_end;
}

void _exit(int return_value)
{
    (void)return_value;
    asm("dsb sy");
    while (1)
    {
        asm("wfi");
    }
}

int _getpid(void)
{
    return 1;
}

int _kill(int pid, int sig)
{
    (void)pid;
    (void)sig;
    errno = EINVAL;
    return -1;
}
